//
// Created by pzw on 24-3-1.
//

#ifndef QTTEST_LINKEDLIST_H
#define QTTEST_LINKEDLIST_H

#include <list>
#include <vector>
#include <iostream>

template<class T>
class LinkedIterator;

template<class T>
class LinkedListIterator;

template<typename E>
class LinkedList {
private:
    std::list<E> vec{};

public:
    LinkedList() = default;
    ~LinkedList() = default;

public:
    bool add(E e);
    void add(int index, E element);
    void addFirst(E e);
    void addLast(E e);
    void clear();
    template<typename T>
    T clone();
    bool contains(E o);
    LinkedIterator<E> descendingIterator();
    E element();
    E get(int index);
    E getFirst();
    E getLast();
    int indexOf(E o);
    int lastIndexOf(E o);
    LinkedListIterator<E> listIterator();
    bool offer(E e);
    bool offerFirst(E e);
    bool offerLast(E e);
    E *peek();
    E *peekFirst();
    E *peekLast();
    E *poll();
    E *pollFirst();
    E *pollLast();
    E *pop();
    void push(E e);
    bool remove(E &o);
    bool removeFirstOccurrence(E o);
    bool removeLastOccurrence(E o);
    E remove(int index);
    E set(int index, E element);
    int size();
    std::vector<E> toArray();
    std::vector<E> toArray2(LinkedList<E> a);
};

/**
 * 迭代器
 *
 * @tparam T - 模板参数
 */
template<class T>
class LinkedIterator {
private:
    /* 我们直接利用C++的迭代器进行实现，控制一下迭代器的移位时序即可 */
    typename std::list<T>::const_iterator begin;
    typename std::list<T>::const_iterator current;
    typename std::list<T>::const_iterator end;

private:
    std::list<T> &vec;

public:
    explicit LinkedIterator(std::list<T> &vec)
            : begin(vec.begin()), current(vec.begin()), end(vec.end()), vec(vec) {
        /**
         * 注意，这里的初始化列表，与下列的 = 赋值，是不一样的，C++语法真他妈傻逼；
         * 构造器冒号后面的初始化列表，效率要更高；
         */
    }

    explicit LinkedIterator(std::list<T> &vec, size_t index)
            : begin(vec.begin()), current(vec.begin() + index), end(vec.end()) {
        /**
         * 注意，这里的初始化列表，与下列的 = 赋值，是不一样的，C++语法真他妈傻逼；
         * 构造器冒号后面的初始化列表，效率要更高；
         */
    }

    ~LinkedIterator() = default;

    bool hasNext() {
        return current != end;
    }

    T next() {
        if (!hasNext()) {
            // Handle error or throw exception
            return T();
        }
        // 返回当前元素并移动到下一个元素
        T ret = *current;
        current++;
        return ret;
    }

    void remove() {
        if (current != vec.begin()) { // 确保不是在容器的开始位置尝试删除
            // 删除元素，并将迭代器移动到下一个有效元素
            typename std::list<T>::const_iterator &itr = --current;
            current = vec.erase(itr);
        } else {
            std::cout << "Cannot remove before calling next" << std::endl;
        }
    }

};

/**
 * List迭代器
 *
 * @tparam T - 模板参数
 */
template<class T>
class LinkedListIterator {
private:
    typename std::list<T>::iterator begin;
    typename std::list<T>::iterator current;
    typename std::list<T>::iterator end;

private:
    std::list<T> &vec;

public:
    explicit LinkedListIterator(std::list<T> &vec)
            : begin(vec.begin()), current(vec.begin()), end(vec.end()), vec(vec) {
        /**
         * 注意，这里的初始化列表，与下列的 = 赋值，是不一样的，C++语法真他妈傻逼；
         * 构造器冒号后面的初始化列表，效率要更高；
         */
        begin = vec.begin();
        current = vec.begin();
        end = vec.end();
        this->vec = vec;
    }

    explicit LinkedListIterator(std::list<T> &vec, size_t index)
            : begin(vec.begin()), current(vec.begin()), end(vec.end()), vec(vec) {
        /**
         * 注意，这里的初始化列表，与下列的 = 赋值，是不一样的，C++语法真他妈傻逼；
         * 构造器冒号后面的初始化列表，效率要更高；
         */
        begin = vec.begin();
        current = vec.begin() + index;
        end = vec.end();
        this->vec = vec;
    }

    ~LinkedListIterator() = default;

    bool hasNext() {
        return current != end;
    }

    T next() {
        if (!hasNext()) {
            // Handle error or throw exception
            return T();
        }
        // 返回当前元素并移动到下一个元素
        T ret = *current;
        current++;
        return ret;
    }

    void remove() {
        if (current != vec.begin()) { // 确保不是在容器的开始位置尝试删除
            // 删除元素，并将迭代器移动到下一个有效元素
            typename std::list<T>::const_iterator &itr = --current;
            current = vec.erase(itr);
        } else {
            std::cout << "Cannot remove before calling next" << std::endl;
        }
    }

};

int list_api_main();

#endif //QTTEST_LINKEDLIST_H
